package cn.xuewenbao.ucenter.service.impl;

import cn.xuewenbao.ucenter.entity.Member;
import cn.xuewenbao.ucenter.entity.vo.*;
import cn.xuewenbao.ucenter.mapper.MemberMapper;
import cn.xuewenbao.ucenter.service.MemberService;
import cn.xuewenbao.ucenter.utils.JwtUtils;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.extern.slf4j.Slf4j;
import lombok.val;
import org.jeecg.common.api.vo.Result;
import org.jeecg.common.constant.CommonConstant;
;

import org.jeecg.common.util.PasswordUtil;
import org.jeecg.common.util.RedisUtil;
import org.jeecg.common.util.oConvertUtils;
import org.jeecg.modules.base.service.BaseCommonService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;

/**
 * <p>
 * 用户表 服务实现类
 * </p>
 *
 * @author mafayu
 * @since 2021-03-29
 */
@Service
@Slf4j
public class MemberServiceImpl extends ServiceImpl<MemberMapper, Member> implements MemberService {

    @Resource
    private BaseCommonService baseCommonService;

//    @Autowired
//    private BookService bookService;
//
//    @Autowired
//    private CourseService courseService;

    @Autowired
    private MemberMapper memberMapper;

    @Autowired
    private RedisUtil redisUtil;

    //用户表-手机号密码登录
    @Override
    public Result<JSONObject> login(MemberLogin memberLogin) {
        Result<JSONObject> result = new Result<>();
        String mobile = memberLogin.getMobile();
        String password = memberLogin.getPassword();

        //手机号和密码非空判断
        if (StringUtils.isEmpty(mobile) || StringUtils.isEmpty(password)) {
            result.error500("手机号或密码为空");
            return result;
        }

        //校验用户是否有效
        QueryWrapper<Member> wrapper = new QueryWrapper<>();
        wrapper.eq("mobile", mobile);
        Member member = baseMapper.selectOne(wrapper);
        result = checkUserIsEffective(member);
        if (!result.isSuccess()) {
            return result;
        }

        //校验用户名或密码是否正确
        String userpassword = PasswordUtil.encrypt(mobile, password, member.getSalt());
        String syspassword = member.getPassword();
        if (!syspassword.equals(userpassword)) {
            result.error500("手机号或密码错误");
            return result;
        }

        JSONObject obj = new JSONObject();
        //用户登录信息
        obj.put("userInfo", member);

        // 生成token
        String token = JwtUtils.sign(mobile, syspassword);
        // 设置超时时间
        redisUtil.set(CommonConstant.PREFIX_USER_TOKEN + token, token);
        redisUtil.expire(CommonConstant.PREFIX_USER_TOKEN + token, JwtUtils.EXPIRE_TIME * 2 / 1000);

        //token 信息
        obj.put("token", token);
        result.setResult(obj);
        result.setSuccess(true);
        result.setCode(200);
        baseCommonService.addLog("手机号: " + mobile + ",登录成功[移动端]！", CommonConstant.LOG_TYPE_1, null);
        return result;
    }

    //用户表-修改个人资料
    @Override
    public boolean updateMember(MemberUpdate memberUpdate) {
        Member member = new Member();
        BeanUtils.copyProperties(memberUpdate, member);
        int update = baseMapper.updateById(member);
//        articleService.updateCascade(member.getId(),member.getUsername());
        return update > 0;
    }

    //用户表-根据id获取用户信息
    @Override
    public MemberInfoVo getMemberInfo(String memberId) {
        Member member = baseMapper.selectById(memberId);
        MemberInfoVo memberInfoVo = new MemberInfoVo();
        if (member != null) {
            BeanUtils.copyProperties(member, memberInfoVo);
        }
        return memberInfoVo;
    }

    @Override
    public Result<?> resetPassword(String mobile, String oldpassword, String password, String confirmpassword) {
        QueryWrapper<Member> wrapper = new QueryWrapper<>();
        wrapper.eq("mobile", mobile);
        Member member = baseMapper.selectOne(wrapper);
        String passwordEncode = PasswordUtil.encrypt(mobile, oldpassword, member.getSalt());
        if (!member.getPassword().equals(passwordEncode)) {
            return Result.error("旧密码输入错误!");
        }
        if (oConvertUtils.isEmpty(password)) {
            return Result.error("新密码不允许为空!");
        }
        if (!password.equals(confirmpassword)) {
            return Result.error("两次输入密码不一致!");
        }
        String passwordNew = PasswordUtil.encrypt(mobile, password, member.getSalt());
        member.setPassword(passwordNew);
        baseMapper.updateById(member);
        return Result.ok("密码重置成功!");
    }

    //用户表-根据id获取用户信息-用于个人简介
    @Override
    public Result<MemberProfileVo> getMemberProfile(String memberId, String userId) {
        Result<MemberProfileVo> result = new Result<>();
        MemberProfileVo memberProfileVo = memberMapper.selectMemberProfileByMemberIdAndUserId(memberId, userId);
        result.setResult(memberProfileVo);
        result.setSuccess(true);
        return result;
    }

    @Override
    public Member getUserByPhone(String mobile) {
        QueryWrapper<Member> wrapper = new QueryWrapper<>();
        wrapper.eq("mobile", mobile);
        Member member = baseMapper.selectOne(wrapper);
        if (member == null) {
            log.error("用户不存在");
            return null;
        }
        return member;
    }

    @Override
    public Result<String> checkUserEffective(Member member) {
        Result<String> result = new Result<>();
        //情况1：根据用户信息查询，该用户不存在
        if (member == null) {
            result.error500("该用户不存在，请注册");
            baseCommonService.addLog("用户登录失败，用户不存在！", CommonConstant.LOG_TYPE_1, null);
            return result;
        }
        //情况2：根据用户信息查询，该用户已注销
        if (CommonConstant.DEL_FLAG_1.equals(member.getIsDeleted())) {
            //update-end---author:王帅   Date:20200601  for：if条件永远为falsebug------------
            baseCommonService.addLog("用户登录失败，用户名:" + member.getUsername() + "已注销！", CommonConstant.LOG_TYPE_1, null);
            result.error500("该用户已注销");
            return result;
        }
        // todo 情况3：根据用户信息查询，该用户已冻结
        return result;
    }

    @Override
    public Member getUserByName(String username) {
        QueryWrapper<Member> wrapper = new QueryWrapper<>();
        wrapper.eq("mobile", username);
        Member member = baseMapper.selectOne(wrapper);
        if (member == null) {
            log.error("用户不存在");
            return null;
        }
        return member;
    }

    //注册时确认密码
    @Override
    public Result<JSONObject> register(RegisterVo registerVo) {
        Result<JSONObject> result = new Result<>();
        final val mobile = registerVo.getMobile();
        final val password = registerVo.getPassword();
        final val username = registerVo.getUsername();

        QueryWrapper<Member> wrapper = new QueryWrapper<>();
        wrapper.eq("mobile", mobile);
        Member member = baseMapper.selectOne(wrapper);


        String salt = oConvertUtils.randomGen(8);
        String passwordEncode = PasswordUtil.encrypt(mobile, password, salt);
        member.setSalt(salt);
        member.setPassword(passwordEncode);
        member.setUsername(username);
        baseMapper.updateById(member);

        JSONObject obj = new JSONObject();
        //用户登录信息
        obj.put("userInfo", member);

        // 生成token
        String token = JwtUtils.sign(mobile, member.getPassword());
        // 设置超时时间
        redisUtil.set(CommonConstant.PREFIX_USER_TOKEN + token, token);
        redisUtil.expire(CommonConstant.PREFIX_USER_TOKEN + token, JwtUtils.EXPIRE_TIME * 2 / 1000);

        //token 信息
        obj.put("token", token);
        result.setResult(obj);
        result.setSuccess(true);
        result.setCode(200);
        baseCommonService.addLog("手机号: " + mobile + ",登录成功[移动端]！", CommonConstant.LOG_TYPE_1, null);
        return result;

    }

    @Override
    public Integer getTotalUserNumber() {
        return baseMapper.selectCount(null);
    }

//    @Override
//    public Result<List<IntroduceVo>> personalIntroduce(String userId) {
//        Result<List<IntroduceVo>> result=new Result<>();
//        List<IntroduceVo> list=new ArrayList<>();
//        //获取讲书前两个
//        QueryWrapper<Book> bookQueryWrapper=new QueryWrapper<>();
//        bookQueryWrapper.orderByDesc("view_count");
//        bookQueryWrapper.last("limit 2");
//        List<Book> bookList=bookService.list(bookQueryWrapper);
//        for (Book book : bookList) {
//            IntroduceVo introduceVo=new IntroduceVo();
//            BeanUtils.copyProperties(book,introduceVo);
//            list.add(introduceVo);
//        }
//        //获取课程前两个
//        QueryWrapper<Course> courseQueryWrapper=new QueryWrapper<>();
//        courseQueryWrapper.orderByDesc("buy_count");
//        courseQueryWrapper.last("limit 2");
//        List<Course> courseList=courseService.list(courseQueryWrapper);
//        for (Course course : courseList) {
//            IntroduceVo introduceVo=new IntroduceVo();
//            BeanUtils.copyProperties(course,introduceVo);
//            list.add(introduceVo);
//        }
//        result.setSuccess(true);
//        result.setResult(list);
//        return result;
//    }


    public Result<JSONObject> checkUserIsEffective(Member member) {
        Result<JSONObject> result = new Result<>();
        //情况1：根据用户信息查询，该用户不存在
        if (member == null) {
            result.error500("该用户不存在，请注册");
            baseCommonService.addLog("用户登录失败，用户不存在！", CommonConstant.LOG_TYPE_1, null);
            return result;
        }
        //情况2：根据用户信息查询，该用户已注销
        if (CommonConstant.DEL_FLAG_1.equals(member.getIsDeleted())) {
            //update-end---author:王帅   Date:20200601  for：if条件永远为falsebug------------
            baseCommonService.addLog("用户登录失败，用户名:" + member.getUsername() + "已注销！", CommonConstant.LOG_TYPE_1, null);
            result.error500("该用户已注销");
            return result;
        }
        // todo 情况3：根据用户信息查询，该用户已冻结
        return result;
    }

    @Override
    public String getUserNameById(String Id){
        Member member = baseMapper.selectById(Id);
        return member.getUsername();
    }

}
